package com.jumi.microservice.controller;

import com.jumi.microservice.common.base.BaseController;
import com.jumi.microservice.common.base.dto.BasePageResponse;
import com.jumi.microservice.common.base.dto.ResponseResult;
import com.jumi.microservice.common.redis.RedisCache;
import com.jumi.microservice.common.utils.ObjectUtils;
import com.jumi.microservice.common.utils.ResultGenerator;
import com.jumi.microservice.constant.ExceptionEnum;
import com.jumi.microservice.constant.GoodsKeyConstant;
import com.jumi.microservice.constant.NumberConstant;
import com.jumi.microservice.domain.*;
import com.jumi.microservice.service.GoodsInventoryApi;
import com.jumi.microservice.service.GoodsSkuService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.Reference;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.util.*;
import java.util.stream.Collectors;

/**
 * 商品sku管理controller组件
 *
 * @author Administrator
 */
@RestController
@Api(tags = "商品sku管理接口")
@RequestMapping("/commodity/goods/sku")
public class GoodsSkuController extends BaseController {

    /**
     * 商品sku管理service组件
     */
    @Autowired
    private GoodsSkuService goodsSkuService;

    /**
     * 库存管理service组件
     */
    @DubboReference
    private GoodsInventoryApi goodsInventoryApi;

    @Autowired
    private RedisCache redisCache;

    /**
     * 分页查询商品sku
     *
     * @param goodsSkuQuery 商品sku查询条件
     * @return GoodsSkuVO集合
     */
    @ApiOperation(value = "分页查询商品sku", notes = "分页查询商品sku")
    @GetMapping("/list")
    public BasePageResponse<List<GoodsSkuVO>> listGoodsSkuByPage(GoodsSkuQuery goodsSkuQuery) {
        List<GoodsSkuVO> goodsVoList =
                convertGoodsSkuDtoList2VoList(goodsSkuService.listGoodsSkuByPage(goodsSkuQuery));

        List<Long> goodsSkuIds = new ArrayList<>();
        for (GoodsSkuVO goodsSku : goodsVoList) {
            goodsSkuIds.add(goodsSku.getId());
        }

        if (goodsSkuIds.size() > NumberConstant.NUMBER_ZERO.intValue()) {
            List<GoodsSpuInventoryDTO> goodsSpuInventories = goodsInventoryApi.goodsInventoryBySkuIds(goodsSkuIds);

            Map<Long, GoodsSpuInventoryDTO> goodsSpuInventoriesMap = new HashMap<>();

            if (goodsSpuInventories != null && goodsSpuInventories.size() > NumberConstant.NUMBER_ZERO.intValue()) {
                goodsSpuInventories.forEach(goodsSpuInventoryDTO -> {
                    goodsSpuInventoriesMap.put(goodsSpuInventoryDTO.getSkuId(),goodsSpuInventoryDTO);
                });

                for (GoodsSkuVO goodsSku : goodsVoList) {
                    if (goodsSpuInventoriesMap.containsKey(goodsSku.getId())) {
                        goodsSku.setPreStorage(goodsSpuInventoriesMap.get(goodsSku.getId()).getPreStorage());
                        goodsSku.setSaledStorage(goodsSpuInventoriesMap.get(goodsSku.getId()).getSaledStorage());
                    } else {
                        goodsSku.setPreStorage(NumberConstant.NUMBER_ZERO.intValue());
                        goodsSku.setSaledStorage(NumberConstant.NUMBER_ZERO.intValue());
                    }
                }
            }
        }

        return ResultGenerator.genSuccessResultPage(
                goodsVoList.stream()
                        .skip(goodsSkuQuery.getPageSize() * (goodsSkuQuery.getPageNum() - 1))
                        .limit(goodsSkuQuery.getPageSize()).collect(Collectors.toList())
                , Long.valueOf(goodsVoList.size()));
    }

    /**
     * 查询是否开启虚拟销量
     */
    @ApiOperation(value = "查询是否开启虚拟销量", notes = "查询是否开启虚拟销量")
    @GetMapping("/queryVirtualNum")
    public ResponseResult<Boolean> queryVirtualNum() {
        boolean virtualNum = Boolean.FALSE;

        Object cacheObject = redisCache.getCacheObject(GoodsKeyConstant.GOODS_VIRTUALNUM_KEY);
        if (Objects.nonNull(cacheObject)) {
            if (cacheObject.equals(NumberConstant.NUMBER_ONE.intValue())) {
                virtualNum = Boolean.TRUE;
            }
        }
        return ResultGenerator.genSuccessResult(virtualNum);
    }

    /**
     * 是否开启虚拟销量
     *
     * @param enableVirtualNum 是否开启虚拟销量
     * @param request          HttpServletRequest
     */
    @ApiOperation(value = "是否开启虚拟销量", notes = "是否开启虚拟销量")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "virtualNum", value = "虚拟销量")
    })
    @PutMapping("/enableVirtualNum")
    public ResponseResult<Boolean> enableVirtualNum(@RequestParam("enableVirtualNum") Integer enableVirtualNum,
                                                    HttpServletRequest request) {
        redisCache.setCacheObject(GoodsKeyConstant.GOODS_VIRTUALNUM_KEY, enableVirtualNum);
        return ResultGenerator.genSuccessResult(Boolean.TRUE);
    }

    /**
     * 编辑虚拟销量
     *
     * @param id         商品sku id
     * @param virtualNum 虚拟销量
     * @param request    HttpServletRequest
     */
    @ApiOperation(value = "商品sku的虚拟销量", notes = "商品sku的虚拟销量")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "id", value = "商品sku id"),
            @ApiImplicitParam(name = "virtualNum", value = "虚拟销量")
    })
    @PutMapping("/update")
    public ResponseResult<Boolean> updateVirtualNum(@RequestParam("id") String id, @RequestParam("virtualNum") Integer virtualNum,
                                                    HttpServletRequest request) {
        goodsSkuService.updateVirtualNum(id, virtualNum, request);
        return ResultGenerator.genSuccessResult(Boolean.TRUE);
    }

    /**
     * 根据第三方商品spu id查询sku集合设置成本价
     *
     * @param id 第三方商品spu id
     * @return GoodsSkuVO集合
     */
    @ApiOperation(value = "查询商品sku设置成本价", notes = "查询商品sku设置成本价")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "id", value = "商品spu id"),
    })
    @GetMapping("/list/{id}")
    public ResponseResult<List<GoodsSkuVO>> listGoodsSku(@PathVariable("id") Long id) {
        List<GoodsSkuDTO> goodsDtoList = goodsSkuService.listGoodsSku(id);
        return ResultGenerator.genSuccessResult(convertGoodsSkuDtoList2VoList(goodsDtoList));
    }

    /**
     * 第三方商品spu设置成本价
     *
     * @param goodsSkus 第三方商品spu集合
     * @return 结果
     */
    @ApiOperation(value = "商品sku集合设置成本价", notes = "商品sku集合设置成本价")
    @PutMapping("/setGoodsSkuCostprice")
    public ResponseResult<Boolean> setGoodsSkuCostprice(@RequestBody List<GoodsSkuVO> goodsSkus, HttpServletRequest request) {
        goodsSkuService.setGoodsSkuCostPrice(convertGoodsSkuVoList2DtoList(goodsSkus), request);
        return ResultGenerator.genSuccessResult(Boolean.TRUE);
    }

    /**
     * 根据skuid查询sku分仓明细数据
     *
     * @param skuId 商品skuId
     * @return 结果
     */
    @ApiOperation(value = "根据skuid查询sku分仓明细数据", notes = "根据skuid查询sku分仓明细数据")
    @GetMapping("/listSkuWarehouseStockDetail/{skuId}")
    public ResponseResult<List<SkuWarehouseStockVO>> listSkuWarehouseStockDetail(@PathVariable("skuId") Long skuId) {
        List<SkuWarehouseStockDTO> skuWarehouseStocks = goodsInventoryApi.listSkuWarehouseStockDetail(skuId);
        return ResultGenerator.genSuccessResult(convertSkuWarehouseStockDtoList2VoList(skuWarehouseStocks));
    }

    /**
     * 将商品sku 仓库DTO对象集合转换为VO对象集合
     *
     * @param goods 商品sku 仓库DTO集合
     * @return List<SkuWarehouseStockVO> 商品仓库VO对象集合
     */
    private List<SkuWarehouseStockVO> convertSkuWarehouseStockDtoList2VoList(List<SkuWarehouseStockDTO> goods) {
        List<SkuWarehouseStockVO> goodsSkuVoList = null;
        try {
            goodsSkuVoList = ObjectUtils.convertList(goods, SkuWarehouseStockVO.class);
        } catch (Exception e) {
            ExceptionEnum.FAIL_CHANGE.newException();
        }
        return goodsSkuVoList;
    }

    /**
     * 将商品sku DTO对象集合转换为VO对象集合
     *
     * @param goods 商品sku DTO集合
     * @return List<GoodsSkuVO> 商品VO对象集合
     */
    private List<GoodsSkuVO> convertGoodsSkuDtoList2VoList(List<GoodsSkuDTO> goods) {
        List<GoodsSkuVO> goodsSkuVoList = null;
        try {
            goodsSkuVoList = ObjectUtils.convertList(goods, GoodsSkuVO.class);
        } catch (Exception e) {
            ExceptionEnum.FAIL_CHANGE.newException();
        }
        return goodsSkuVoList;
    }

    /**
     * 将商品sku VO对象集合转换为DTO对象集合
     *
     * @param goods 商品sku DTO集合
     * @return List<GoodsSkuVO> 商品VO对象集合
     */
    private List<GoodsSkuDTO> convertGoodsSkuVoList2DtoList(List<GoodsSkuVO> goods) {
        List<GoodsSkuDTO> goodsSkuDtoList = null;
        try {
            goodsSkuDtoList = ObjectUtils.convertList(goods, GoodsSkuDTO.class);
        } catch (Exception e) {
            ExceptionEnum.FAIL_CHANGE.newException();
        }
        return goodsSkuDtoList;
    }

    /**
     * 将商品sku VO对象集合转换为DTO对象集合
     *
     * @param goods 商品skuVO集合
     * @return List<GoodsSkuInventoryDTO> 商品VO对象集合
     */
    private List<GoodsSkuInventoryDTO> convertGoodsSkuInventoryVoList2DtoList(List<GoodsSkuInventoryVO> goods) {
        List<GoodsSkuInventoryDTO> goodsSkuInventoryDtoList = null;
        try {
            goodsSkuInventoryDtoList = ObjectUtils.convertList(goods, GoodsSkuInventoryDTO.class);
        } catch (Exception e) {
            ExceptionEnum.FAIL_CHANGE.newException();
        }
        return goodsSkuInventoryDtoList;
    }

}
